package demo.db.tsdb.victoriaMetrics;

import demo.db.tsdb.influxDB.InfluxDbDemo;
import demo.db.tsdb.prometheus.PrometheusApi;
import demo.db.tsdb.prometheus.vo.PromRange;
import demo.vo.exp.ServiceException;
import demo.vo.tsdb.DataPoint;
import org.junit.Before;
import org.junit.Test;

import java.io.IOException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.concurrent.TimeUnit;

/**
 * VictoriaMetrics 是一个开源的、高性能的时间序列数据库，它支持Prometheus的查询语言。
 * API:
 */
public class VictoriaMetricsDemo {

    public static String host = "http://192.168.60.89:8428";
    PrometheusApi prometheusApi;

    @Before
    public void setUp() throws Exception {
        prometheusApi = new PrometheusApi(host);
    }

    /**
     * <li> Deletes time series from VictoriaMetrics.
     * <blockquote><pre>
     *     curl -v http://localhost:8428/api/v1/admin/tsdb/delete_series -d 'match[]=vm_http_request_errors_total'
     * </pre></blockquote>
     */
    @Test
    public void testDeleteSeries() {

    }

    /**
     * <blockquote><pre>
     * # 导出json
     * curl http://localhost:8428/api/v1/export -d 'match[]=vm_http_request_errors_total' > filename.json
     * # 导出csv
     * curl http://localhost:8428/api/v1/export/csv -d 'format=__name__,__value__,__timestamp__:unix_s' -d 'match[]=vm_http_request_errors_total' > filename.csv
     * # 导出数据
     * curl http://localhost:8428/api/v1/export/native -d 'match[]=vm_http_request_errors_total' > filename.bin
     * </pre></blockquote>
     */
    @Test
    public void testExport() {

    }

    /**
     * <blockquote><pre>
     * # 导入json
     * curl -H 'Content-Type: application/json' --data-binary "@filename.json" -X POST http://localhost:8428/api/v1/import
     * # 导入csv
     * curl -d "GOOG,1.23,4.56,NYSE" 'http://localhost:8428/api/v1/import/csv?format=2:metric:ask,3:metric:bid,1:label:ticker,4:label:market'
     * # 导入数据
     * curl -X POST http://localhost:8428/api/v1/import/native -T filename.bin
     * # 导入普罗数据
     * curl -d 'metric_name{foo="bar"} 123' -X POST http://localhost:8428/api/v1/import/prometheus
     * </pre></blockquote>
     */
    @Test
    public void testImport() throws ServiceException, IOException {
        String metricName = "test_vm_request_total";
        long now = System.currentTimeMillis();
        Map<String, String> tags = new HashMap<>();
        tags.put("app", "demo-app");
        List<String> data = new ArrayList<>();
        for (int i = 0; i < 10; i++) {
            tags.put("code", "20" + i);
            data.add(PrometheusApi.formatMetric(metricName, i, now, tags));
        }
        prometheusApi.importData(data);
    }

    /**
     * <blockquote><pre>
     * # 查询标签
     * curl http://localhost:8428/prometheus/api/v1/labels
     * # 查询标签值
     * curl http://localhost:8428/prometheus/api/v1/label/job/values
     * </pre></blockquote>
     */
    public void testLabels() {

    }

    /**
     * <blockquote><pre>
     * curl http://localhost:8428/prometheus/api/v1/query -d 'query=vm_http_request_errors_total'
     *
     * curl http://localhost:8428/prometheus/api/v1/query_range -d 'query=sum(increase(vm_http_request_errors_total{job="foo"}[5m]))' -d 'start=-1d' -d 'step=1h'
     * </pre></blockquote>
     *
     * @throws ServiceException
     * @throws IOException
     */
    @Test
    public void testQuery() throws ServiceException, IOException {
        PrometheusApi api = new PrometheusApi(host);
        // 查询数据
        long now = System.currentTimeMillis();
        long start = now - TimeUnit.HOURS.toMillis(1);
        PromRange promRange = prometheusApi.queryRange2("test_vm_request_total{}", start, now, "10m");
        System.out.println(promRange);
//        String promQL = "sum_over_time(test_vm_request_total)";
//        JSONObject json = api.query(promQL, null);
//        System.out.println(json);
//
//        PromRange res = api.queryRange2(promQL, start, now, "10m");
//        System.out.println(res);
    }


    /**
     * <blockquote><pre>
     * # 查询序列
     * curl http://localhost:8428/prometheus/api/v1/series -d 'match[]=vm_http_request_errors_total'
     * </pre></blockquote>
     */
    public void series() {

    }

    /**
     * <blockquote><pre>
     * curl http://localhost:8428/prometheus/api/v1/status/tsdb
     * </pre></blockquote>
     */
    public void status() {

    }

    /**
     * 可以通过prometheus的http接口/api/v1/write提交数据，这个接口的数据格式有有要求：
     * 使用POST方式提交 需要经过protobuf编码，依赖github.com/gogo/protobuf/proto ;
     * 可以使用snappy进行压缩，依赖github.com/golang/snappy
     *
     * @throws IOException
     * @see <a href='https://www.lxlinux.net/9384.html'>参考</a>
     */
    @Test
    public void testWritePrometheus() throws IOException {
        String url = host + "/api/v1/write";
        String metric = "test_vm_request";
        Map<String, String> tags = new HashMap<>();
        tags.put("app", "app1");
        tags.put("code", "200");
        long now = System.currentTimeMillis();
    }

    /**
     * 通过InfluxDB的line protocol写入数据
     * <blockquote><pre>
     *     curl -d 'measurement,tag1=value1,tag2=value2 field1=123,field2=1.23' -X POST http://localhost:8428/write
     * </pre></blockquote>
     */
    @Test
    public void testWriteInfluxDB() {
        String metric = "test_vm_request";
        Map<String, String> tags = new HashMap<>();
        tags.put("app", "app1");
        tags.put("code", "200");
        long now = System.currentTimeMillis();


        for (int i = 0; i < 60; i++) {
            long time = now - i * TimeUnit.MINUTES.toMillis(1);
            DataPoint data = new DataPoint(time, 1);
            InfluxDbDemo.addPoint(metric, tags, data);
        }
    }


}
